home *** CD-ROM | disk | FTP | other *** search
/ Language/OS - Multiplatform Resource Library / LANGUAGE OS.iso / smaltalk / st80_pr4.lha / st80_pre4 / MoDE / Modes-Shan.st < prev    next >
Text File  |  1993-07-24  |  56KB  |  1,886 lines

  1. Object subclass: #SaveState
  2.     instanceVariableNames: 'cursorIn controller '
  3.     classVariableNames: ''
  4.     poolDictionaries: ''
  5.     category: 'Modes-Shan'!
  6. SaveState comment:
  7. 'The cursorIn has to be stored to prevent the funny hehavior in highlight/deHighlight.  If it is not stored and restored, when one move a highlighted mode under another mode, the highlighted mode will remain highlighted even the cursor now is on top of the other mode and generates cursorMove events.  If the cursorIn is kept, the dragged mode will be sent a leaveMode event to deHighlight itself when the cursorMove events are generated.  Shan July 19, 1989'!
  8.  
  9.  
  10. !SaveState methodsFor: 'private'!
  11.  
  12. controller: c cursorIn: b
  13.     "Shan July 16, 1989"
  14.     controller _ c.
  15.     cursorIn _ b! !
  16.  
  17. !SaveState methodsFor: 'access'!
  18.  
  19. controller 
  20.     ^controller!
  21.  
  22. controller: c
  23.     controller _ c!
  24.  
  25. cursorIn
  26.     ^cursorIn!
  27.  
  28. cursorIn: aBool
  29.     cursorIn _ aBool! !
  30.  
  31. !SaveState methodsFor: 'initialize-release'!
  32.  
  33. release
  34.     controller release! !
  35. "-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- "!
  36.  
  37. SaveState class
  38.     instanceVariableNames: ''!
  39.  
  40.  
  41. !SaveState class methodsFor: 'instance creation'!
  42.  
  43. controller: c cursorIn: b 
  44.     "Shan July 16, 1989"
  45.  
  46.     ^self new controller: c cursorIn: b! !
  47.  
  48. Object subclass: #ResizeStyle
  49.     instanceVariableNames: 'originX originY cornerX cornerY extentX extentY matchViewportWindow '
  50.     classVariableNames: ''
  51.     poolDictionaries: ''
  52.     category: 'Modes-Shan'!
  53. ResizeStyle comment:
  54. 'There can only be two kind of Symbol here--#fixed or #flexible.  Shan June 8, 1989'!
  55.  
  56.  
  57. !ResizeStyle methodsFor: 'initialize'!
  58.  
  59. initialize
  60.     "Shan June 8, 1989"
  61.  
  62.     originX _ #flexible.
  63.     originY _ #flexible.
  64.     cornerX _ #flexible.
  65.     cornerY _ #flexible.
  66.     extentX _ #flexible.
  67.     extentY _ #flexible.
  68.     matchViewportWindow _ false! !
  69.  
  70. !ResizeStyle methodsFor: 'access'!
  71.  
  72. cornerX
  73.     ^cornerX!
  74.  
  75. cornerX: aSymbol
  76.     cornerX _ aSymbol!
  77.  
  78. cornerY
  79.     ^cornerY!
  80.  
  81. cornerY: aSymbol
  82.     cornerY _ aSymbol!
  83.  
  84. extentX
  85.     ^extentX!
  86.  
  87. extentX: aSymbol
  88.     extentX _ aSymbol!
  89.  
  90. extentY
  91.     ^extentY!
  92.  
  93. extentY: aSymbol
  94.     extentY _ aSymbol!
  95.  
  96. matchViewportWindow
  97.     ^matchViewportWindow!
  98.  
  99. matchViewportWindow: aBoolean
  100.     matchViewportWindow _ aBoolean!
  101.  
  102. originX
  103.     ^originX!
  104.  
  105. originX: aSymbol
  106.     originX _ aSymbol!
  107.  
  108. originY
  109.     ^originY!
  110.  
  111. originY: aSymbol
  112.     originY _ aSymbol! !
  113.  
  114. !ResizeStyle methodsFor: 'popular styles'!
  115.  
  116. stickFourCorners
  117.     "Shan September 28, 1989"
  118.  
  119.     self matchViewportWindow: true.
  120.     self originX: #fixed.
  121.     self originY: #fixed.
  122.     self cornerX: #fixed.
  123.     self cornerY: #fixed! !
  124. "-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- "!
  125.  
  126. ResizeStyle class
  127.     instanceVariableNames: ''!
  128.  
  129.  
  130. !ResizeStyle class methodsFor: 'constants'!
  131.  
  132. stickFourCorners
  133.     "Shan September 28, 1989"
  134.  
  135.     ^self new stickFourCorners! !
  136.  
  137. !ResizeStyle class methodsFor: 'instance creation'!
  138.  
  139. new
  140.     "Shan June 8, 1989"
  141.  
  142.     ^super new initialize! !
  143.  
  144. View subclass: #Mode
  145.     instanceVariableNames: 'cursorIn obscuringRects visible dispObj highlightDispObj resizeStyle highlighted savedStates '
  146.     classVariableNames: ''
  147.     poolDictionaries: ''
  148.     category: 'Modes-Shan'!
  149.  
  150.  
  151. !Mode methodsFor: 'displaying-private'!
  152.  
  153. displayModesInFrontOf: aMode 
  154.     ^self
  155.         displayModesInFrontOf: aMode
  156.         on: Display
  157.         in: nil!
  158.  
  159. displayModesInFrontOf: aMode on: aMedium in: aRect 
  160.     "This is for painter modes and modes that has other modes with   
  161.     insideColor nil on top of them.  This should cut the search in half and 
  162.     therefore give %50 better preformance.  Shan July 17, 1989"
  163.  
  164.     | found |
  165.     found _ false.
  166.     subViews do: 
  167.         [:aSubView | 
  168.         found ifTrue: [aSubView displayOn: aMedium in: aRect].
  169.         aSubView == aMode ifTrue: [found _ true]].
  170.     superView
  171.         displayModesInFrontOf: self
  172.         on: aMedium
  173.         in: aRect!
  174.  
  175. getVisibleRectsIn: aRect 
  176.     " Shan - 10 December 1988"
  177.     "Add cliping.  Get the visible rects within aRect. Shan March 17, 1989"
  178.     "self halt."
  179.  
  180.     | dispBox |
  181.     dispBox _ self displayBox.
  182.     (dispBox intersects: dispBox)
  183.         ifFalse: ["This is a negative rect. Shan April 6, 1989"
  184.             ^OrderedCollection new: 0].
  185.     aRect notNil
  186.         ifTrue: [(dispBox intersects: aRect)
  187.                 ifTrue: [^self visibleRectsOutOf: (dispBox intersect: aRect)]
  188.                 ifFalse: [^OrderedCollection new: 0]]
  189.         ifFalse: [^self visibleRectsOutOf: dispBox]!
  190.  
  191. visibleRectsOutOf: aRect
  192.     " Shan - 10 December 1988"
  193.     "This method computes a collection of visible rectangles within the aRect."
  194.  
  195.     | visibles newVisibles |
  196.     visibles _ OrderedCollection with: aRect." self halt."
  197.     obscuringRects do: 
  198.         [:eachObscuring | 
  199.         newVisibles _ OrderedCollection new.
  200.         visibles do: [:oldVisible | newVisibles addAll: (oldVisible areasOutside: eachObscuring)].
  201.         newVisibles isEmpty ifTrue: [^newVisibles"Cut down the loop, save some computation"].
  202.         visibles _ newVisibles].
  203.     ^visibles! !
  204.  
  205. !Mode methodsFor: 'displayObject'!
  206.  
  207. displayObject
  208.     ^dispObj!
  209.  
  210. displayObject: aDispObj
  211.     "Assign the display object.  Shan March 23, 1989"
  212.  
  213.     dispObj _ aDispObj!
  214.  
  215. resizeToFitDisplayObject
  216.     "Change the size of the mode to expose all the displayObject.  Shan 
  217.     July 28, 1989"
  218.  
  219.     self resizeToFitDisplayObjectBy: self borderWidth!
  220.  
  221. resizeToFitDisplayObjectBy: delta 
  222.     "Change the size of the mode to expose all the displayObject.  Shan   
  223.     July 28, 1989"
  224.  
  225.     | rect hRect compExt |
  226.     rect _ dispObj boundingBox.
  227.     (highlightDispObj notNil and: [highlightDispObj isKindOf: MDisplayObject])
  228.         ifTrue: [hRect _ highlightDispObj boundingBox].
  229.     "rect isNil
  230.         ifTrue: [hRect isNil
  231.                 ifTrue: [^self]
  232.                 ifFalse: [compExt _ hRect extent]]
  233.         ifFalse: [  Shan March 3, 1990"
  234.     hRect isNil
  235.         ifTrue: [compExt _ rect extent]
  236.         ifFalse: [compExt _ hRect extent max: rect extent].
  237.     self extent: compExt + (delta * 2)! !
  238.  
  239. !Mode methodsFor: 'displaying'!
  240.  
  241. display
  242.     "The logic that cuts down the recursion when self is not visible is       
  243.        added.  Shan March 19, 1989"
  244.  
  245.     | topMode |
  246.     self displayIn: nil.
  247.     (self getVisibleRectsIn: nil)
  248.         do: [:each | superView
  249.                 displayModesInFrontOf: self
  250.                 on: Display
  251.                 in: each]!
  252.  
  253. displayBackgroundIn: aRect 
  254.     "Return false if no portion of self is visible.  Otherwise return true."
  255.     "This version knows how to handle layering.  It clips its output          
  256.       according to the obecuringRects."
  257.     "Shan April 6, 1989"
  258.  
  259.     ^self displayBackgroundOn: Display in: aRect!
  260.  
  261. displayBackgroundOn: aMedium in: aRect 
  262.     "This is for top window buffering.  Shan April 5, 1989"
  263.  
  264.     |  unclippedDispBox  visibleRects |
  265.     visibleRects _ self getVisibleRectsIn: aRect. 
  266.     visibleRects size = 0 ifTrue: [^false].
  267.     unclippedDispBox _ self unclippedDisplayBox.
  268.     dispObj displayOn: aMedium withUnClippedDispBox: unclippedDispBox visibleRects: visibleRects.
  269.     ^true!
  270.  
  271. displayBorder
  272.     "This is a method used for highlighting the mode.  The odd shaped  
  273.     mode problem is not taken care of.  Use with care.  A line on top of  
  274.     the mode can be erased by the border.  Shan April 5, 1989"
  275.  
  276.     | visibleRects unclippedDispBox insetVisibleRects |
  277.     visibleRects _ self getVisibleRectsIn: nil.
  278.     visibleRects size = 0 ifTrue: [^self].
  279.     unclippedDispBox _ self unclippedDisplayBox.
  280.     dispObj borderWithUnClippedDispBox: unclippedDispBox visibleRects: visibleRects.
  281.     visibleRects do: [:each | superView
  282.             displayModesInFrontOf: self
  283.             on: Display
  284.             in: each]!
  285.  
  286. displayIn: aRect 
  287.     "Clip the display to aRect."
  288.     " Shan April 6, 1989"
  289.  
  290.     self displayOn: Display in: aRect!
  291.  
  292. displayOn: aMedium in: aRect 
  293.     "Clip the display to aRect."
  294.     " Shan April 6, 1989"
  295.  
  296.     visible ifTrue: [(self displayBackgroundOn: aMedium in: aRect)
  297.             ifTrue: [self displaySubViewsOn: aMedium in: aRect]]!
  298.  
  299. displaySubViewsIn: aRect
  300.     "Display all the subViews of the receiver clipped to aRect."
  301.     "Shan April 6, 1989"
  302.  
  303.     self displaySubViewsOn: Display in: aRect!
  304.  
  305. displaySubViewsOn: aMedium in: aRect
  306.     "Display all the subViews of the receiver clipped to aRect."
  307.     "Shan March 17, 1989"
  308.  
  309.     subViews do: [:aSubView | aSubView displayOn: aMedium in: aRect]!
  310.  
  311. erase
  312.     "Erase self but do not remove from the mode hierarchy."
  313.     " Shan March 19, 1989"
  314.  
  315.     | topMode savedVisible |
  316. "visible ifFalse: [^self]."
  317.     (dispObj isKindOf: AnimationDispObj)
  318.         ifTrue: [dispObj stopDisplayLoop].
  319.     "Shan May 31, 1989"
  320. savedVisible _ self isVisible.
  321. self setVisible: false.
  322.     topMode _ self topMode.
  323.     (self getVisibleRectsIn: nil)
  324.         do: [:each | topMode displayIn: each].
  325. "Shan September 19, 1989"
  326. self setVisible: "true" savedVisible!
  327.  
  328. scaledBackground
  329.     "Display background with saling.  This is done by assigning the dispObj 
  330.      a bounding box so that when my displayBox is changed, I can scale  
  331.     the background according to the difference between the current  
  332.     displayBox and the boundingBox of the dispObj.  Make some 
  333.     adjustment to avoid floating point transformations.  Shan May 12, 
  334.     1989 "
  335.  
  336.     self displayObject boundingBox: (0 @ 0 extent: self window extent"Modified according to the chnages made in DispObj.  Shan December 1, 1989   - (self borderWidth * 2)")! !
  337.  
  338. !Mode methodsFor: 'drag support'!
  339.  
  340. afterDrag: aSymbol 
  341.     "This is sent by the drag loop after the drag finishes. Shan July 13,  
  342.     1989"
  343.  
  344.     self map.
  345.     self topMode recoverFromDrag: aSymbol!
  346.  
  347. beforeDrag: aSymbol
  348.     "This is sent by the drag loop before the drag starts.  Mode should   
  349.     set up the right controller for the dragging and propagate the   
  350.     message down the mode hierarchy.  Shan June 25, 1989"
  351.     "aSymbol can be #move or #link.  Shan July 13, 1989"
  352.  
  353.     self map.
  354.     "MoveImage erases (and therefore set the mode to invisible) before 
  355.     drag.  Shan July 14, 1989"
  356.     self topMode prepareForDrag: aSymbol.
  357.     "To avoid my controller from processing any events, especially the 
  358.     enter/leave.  Without this, there will be an extra enterMode event 
  359.     generated by the old controller which thinks the cursor has moved 
  360.     out of the area of the mode.  Also avoid my own drag controller from
  361.     obscuring the process of events of the modes under me. Shan July 13,
  362.      1989"
  363.     aSymbol = #move ifTrue: [self unMap.]!
  364.  
  365. prepareForDrag: aSymbol 
  366.     "Remember to propagate the changes here to PollingEnvMode.  Shan July 12, 1989"
  367.  
  368.     savedStates _ SaveState controller: self controller cursorIn: cursorIn.
  369.     model isNil
  370.         ifTrue: [self controller: OpaqueController1 new]
  371.         ifFalse: [self controller: (model dragControllerFor: aSymbol)].
  372.     subViews notNil ifTrue: [subViews do: [:each | each isVisible ifTrue: [each prepareForDrag: aSymbol]]]!
  373.  
  374. recoverFromDrag: aSymbol
  375.     "Set up the normal controller.  Shan July 11, 1989"
  376.     "Currently the aSymbol is redundant.  It may be of other use later.  Shan July 13, 1989"
  377.  
  378.     savedStates isNil ifTrue: [^self].
  379.     self controller: savedStates controller.
  380.     cursorIn _ savedStates cursorIn. "This has to be there to make sure the highlight of modes be correct.  Shan July 21, 1989"
  381.     savedStates _ nil.
  382.     "It is very dangerous to assume that the visibility will not change  
  383.     during drag.  It is safe so far.  Shan June 11, 1989"
  384.     "Use the savedStates to verify whether this mode needs recovery.  Shan July 17, 1989"
  385.     subViews notNil ifTrue: [subViews do: [:each | each recoverFromDrag: aSymbol]]! !
  386.  
  387. !Mode methodsFor: 'scroll support'!
  388.  
  389. contentsBoundingBox
  390.     "Use 0@0 as origin to prevent losing the left and top margin.  Shan 
  391.     Juen 23, 1989"
  392.  
  393.     | aRectangle |
  394.     aRectangle _ 0 @ 0 corner: 0 @ 0.
  395.     subViews do: [:aView | aRectangle _ aRectangle merge: aView viewport].
  396.     ^aRectangle merge: self window! !
  397.  
  398. !Mode methodsFor: 'subMode access'!
  399.  
  400. firstModeAt: p 
  401.     "This is different than the subModeContaining: method in that it  
  402.     searches the whole mode hierarchy.  Shan August 16, 1989"
  403.  
  404.     ^self firstModeAt: p suchThat: [:theMode | true]!
  405.  
  406. firstModeAt: p suchThat: aBlock 
  407.     "This is different than the subModeContaining: method in that it  
  408.     searches the whole mode hierarchy.  Shan August 16, 1989"
  409.  
  410.     ^self firstModeAt: p suchThat: aBlock cutOff: OrderedCollection new!
  411.  
  412. firstModeAt: p suchThat: aBlock cutOff: aCltnOfMode 
  413.     "aCltnOfMode provides the root of the subtrees that we don't want 
  414.     to search.  Shan September 18, 1989"
  415.  
  416.     | m |
  417.     (aCltnOfMode includes: self)
  418.         ifTrue: [^nil].
  419.     visible & (self displayBox containsPoint: p) ifFalse: [^nil].
  420.     subViews isNil ifTrue: [(aBlock value: self)
  421.             ifTrue: [^self]
  422.             ifFalse: [^nil]].
  423.     subViews
  424.         reverseDo: 
  425.             [:each | 
  426.             m _ each firstModeAt: p suchThat: aBlock cutOff: aCltnOfMode.
  427.             m notNil ifTrue: [^m]].
  428.     (aBlock value: self)
  429.         ifTrue: [^self]
  430.         ifFalse: [^nil]!
  431.  
  432. firstModeCovering: aRect 
  433.     "The top subMode with the displayBox contains the aRect.  Shan 
  434.     August 1, 1989"
  435.  
  436.     ^self firstModeCovering: aRect suchThat: [:theMode | true]!
  437.  
  438. firstModeCovering: aRect suchThat: aBlock
  439.     "The top subMode with the displayBox contains the aRect and satisfies the aBlock.  Shan August 10, 1989"
  440.  
  441.     | m |
  442.     visible & (self displayBox contains: aRect) ifFalse: [^nil].
  443.     subViews isNil ifTrue: [(aBlock value: self) ifTrue: [^self] ifFalse: [^nil]].
  444.     subViews
  445.         reverseDo: 
  446.             [:each | 
  447.             m _ each firstModeCovering: aRect suchThat: aBlock.
  448.             m notNil ifTrue: [^m]].
  449.     (aBlock value: self) ifTrue: [^self] ifFalse: [^nil]!
  450.  
  451. firstSubMode
  452.     "Shan June 13, 1989"
  453.  
  454.     ^self firstSubView!
  455.  
  456. lastSubMode
  457.     ^self lastSubView!
  458.  
  459. subModeContaining: aPoint 
  460.     "Shan July 16, 1989"
  461.  
  462.     subViews reverseDo: [:aSubView | aSubView isVisible & (aSubView displayBox containsPoint: aPoint) ifTrue: [^aSubView]].
  463.     ^nil!
  464.  
  465. subModes
  466.     ^subViews! !
  467.  
  468. !Mode methodsFor: 'superMode access'!
  469.  
  470. isTopMode
  471.     "Shan Mrach 17, 1989"
  472.  
  473.     ^ false!
  474.  
  475. superMode
  476.     "Shan June 15, 1989"
  477.  
  478.     ^self superView!
  479.  
  480. topMode
  481.     "Shan Mrach 17, 1989"
  482.  
  483.     ^superView topMode! !
  484.  
  485. !Mode methodsFor: 'layer manipulation'!
  486.  
  487. eraseAndUnMap
  488.     "Shan July 28, 1989"
  489.  
  490.     self erase.
  491.     self unMap!
  492.  
  493. map
  494.     "Make a mode active. Shan July 28, 1989"
  495.  
  496.     self setVisible: true.
  497.     self computeLayering.
  498.     self insideColor notNil ifTrue: ["A transparent mode (insideColor nil) does not affect the clipping of other modes. Shan April 12, 1989"
  499.         self superMode notNil ifTrue: [self superMode computeSubLayeringBelow: self withIn: self displayBox]]!
  500.  
  501. mapAndDisplay
  502.     "Shan July 28, 1989"
  503.  
  504.     self map.
  505.     self display!
  506.  
  507. moveBy: aPoint 
  508.     "Mode the origin of self by aPoint.  No layering relation 
  509.     changed.  Shan March 29, 1989"
  510.     "Does not erase"
  511.  
  512.     self setUnclippedDisplayBoxOrigin: (self unclippedDisplayBox origin + aPoint)!
  513.  
  514. moveRelativeTo: aPoint 
  515.     "Mode the origin of self to the point aPoint in superView's 
  516.     coordinates.  No layering relation changed.  Shan June 1, 1989"
  517.     "Does not erase"
  518.  
  519.     self window: (self window) viewport: (self viewport moveTo: aPoint).
  520.     "For roaming.  Shan June 23, 1989"
  521.     superView changed: #contentsBoundingBoxMayBeChanged!
  522.  
  523. moveTo: aPoint 
  524.     "Mode the origin of self to the absolute point aPoint.  No  
  525.     layering relation changed."
  526.     "Shan March 17, 1989"
  527.     "Does not erase"
  528.  
  529.     self setUnclippedDisplayBoxOrigin: aPoint!
  530.  
  531. moveToBack
  532.     "Make self the back most subMode of the superMode."
  533.     "Shan April 8, 1989"
  534.  
  535.     | savedSuperView |
  536.     savedSuperView _ superView.
  537.     savedSuperView ~= nil
  538.         ifTrue: 
  539.             [savedSuperView removeSubMode: self.
  540.             "Layering is taken care of by the subMode insert/delete 
  541.             methods. "
  542.             savedSuperView addToBackSubMode: self]!
  543.  
  544. moveToFront
  545.     "Make self the front mode subMode of the superMode."
  546.     "Shan March 17, 1989"
  547.  
  548.     | savedSuperView |
  549.     savedSuperView _ superView.
  550.     superView ~= nil
  551.         ifTrue: 
  552.             [self removeFromSuperView.
  553.             "superView is now nil"
  554.             savedSuperView addSubMode: self]!
  555.  
  556. toBack
  557.     "Make self the back most subMode of the superMode and display."
  558.     "Shan June 16, 1989"
  559.  
  560.     self ~~ superView firstSubMode
  561.         ifTrue: 
  562.             [self moveToBack.
  563.             superView displayIn: self displayBox]!
  564.  
  565. toFront
  566.     "Make self the front mode subMode of the superMode and display."
  567.     "Shan June 16, 1989"
  568.  
  569.     self ~~ superView lastSubMode
  570.         ifTrue: 
  571.             [self moveToFront.
  572.             self display]!
  573.  
  574. unMap
  575.     "Make a mode inactive.  Also clear the cursorIn.  Shan July 28, 1989"
  576.  
  577.     self setVisible: false.
  578.     self clearCursorIn! !
  579.  
  580. !Mode methodsFor: 'layering'!
  581.  
  582. computeLayering
  583.     "This is a recursive method to update the obscuringRects when the    
  584.     screen layout is changed. Shan April 23, 1989"
  585.  
  586.     | list |
  587.     list _ OrderedCollection new.
  588.     superView notNil ifTrue: [superView subViews reverseDo: [:each | each == self
  589.                 ifTrue: [^self computeLayering: list withIn: nil]
  590.                 ifFalse: ["A superView must be an ExpandedMode. It is safe to  
  591.                     ask whether it uses painter algorithm or not. Shan  
  592.                     May 11, 1989"
  593.                     "Mode understands the protocol also.  Shan July 21, 
  594.                     1989 "
  595.                     (superView isPainter not and: [each isVisible & each insideColor notNil])
  596.                         ifTrue: [list addLast: each displayBox]]]]!
  597.  
  598. computeLayering: aRectCltn withIn: aRect 
  599.     "Take a collection of peer drawing displayBoxes that may obscure   
  600.     self to compute the obscuringRects.  Make the computation recursive."
  601.     " Shan - 10 December 1988"
  602.     "Add the conditions to handle the odd shaped modes.  Shan April 8, 
  603.     1989 "
  604.     "aRect defines the affected area.  If nil, compute everything. Shan 
  605.     April 17, 1989"
  606.  
  607.     | dispB |
  608. self isVisible ifFalse: [^self].  "Don't compute if not visible.  Shan 13 June 1990"
  609.     dispB _ self displayBox.
  610.     (aRect notNil and: [(dispB intersects: aRect) not])
  611.         ifTrue: [^self].
  612.     obscuringRects _ OrderedCollection new: 1.
  613.     (superView ~= nil and: [superView obscuringRects ~= nil])
  614.         ifTrue: [superView obscuringRects do: [:eachRect | (eachRect intersects: dispB)
  615.                     ifTrue: [obscuringRects addLast: (eachRect intersect: dispB)]]].
  616.     aRectCltn do: [:each | (each intersects: dispB)
  617.             ifTrue: [obscuringRects addLast: (each intersect: dispB)]].
  618.     "Now take care of the subViews."
  619.     "Shan April 23, 1989"
  620.     self computeSubLayeringWithIn: aRect!
  621.  
  622. computeSubLayering
  623.     "Compute the layering of subModes."
  624.     "Shan April 8, 1989"
  625.  
  626.     self computeSubLayeringBelow: nil withIn: nil!
  627.  
  628. computeSubLayeringBelow: aSubView 
  629.     "Shan April 23, 1989"
  630.  
  631.     self computeSubLayeringBelow: aSubView withIn: nil!
  632.  
  633. computeSubLayeringBelow: aSubView withIn: aRect 
  634.     "Tell the subViews that are below aSubView to compute their         
  635.     obscuringRects.  This is used when a subView moves and wants to    
  636.        notifies its peers to recompute the laying relation."
  637.     " Shan March 19, 1989"
  638.     "aRect defines the region that is affected.  Shan April 17, 1989"
  639.  
  640.     | subList found |
  641.     aSubView isNil
  642.         ifTrue: [found _ true
  643.             "compute everyone"]
  644.         ifFalse: [found _ false].
  645.     subViews ~= nil
  646.         ifTrue: 
  647.             [subList _ OrderedCollection new.
  648.             subViews
  649.                 reverseDo: 
  650.                     [:each | 
  651.                     found
  652.                         ifTrue: [each computeLayering: subList withIn: aRect]
  653.                         ifFalse: [each = aSubView ifTrue: [found _ true]].
  654.                     each isVisible & each insideColor notNil ifTrue: [subList add: each displayBox]]]!
  655.  
  656. computeSubLayeringWithIn: aRect 
  657.     "Shan April 23, 1989"
  658.  
  659.     self computeSubLayeringBelow: nil withIn: aRect!
  660.  
  661. isPainter
  662.     "Painter's aglorithm is not supported here.  Shan July 21, 1989"
  663.  
  664.     ^ false!
  665.  
  666. obscuringRects
  667.     "Return the coloection of rectangles that obscure self."
  668.     " Shan - 10 December 1988"
  669.  
  670.     ^obscuringRects!
  671.  
  672. setPainter: aBool 
  673.     "Only an ExpandedMode has the painter's alg. service.  Shan July 21, 1989"
  674.  
  675.     self error: 'Mode does not support painter''s algorithm.  Use ExpandedMode.'! !
  676.  
  677. !Mode methodsFor: 'window access'!
  678.  
  679. defaultWindow
  680.     "This one override the method defined in View.  Shan March 28, 1989"
  681.  
  682.     ^0 @ 0 extent: 100 @ 100! !
  683.  
  684. !Mode methodsFor: 'initialize-release'!
  685.  
  686. initialize
  687.      " Shan - 10 December 1988"
  688.     dispObj _ MDisplayObject new.
  689.     super initialize.
  690.     obscuringRects _ OrderedCollection new: 0.
  691.     cursorIn _ false.
  692.     visible _ true.
  693.     highlighted _ false.
  694.     "Shan July 17, 1989"!
  695.  
  696. release
  697.     "This is to inform the semantic object to do the final clean up.  Shan 
  698.     June 2, 1989"
  699.  
  700.     savedStates release.
  701.     "savedStates _ nil."  "Shan June 26, 1989"
  702.     model release. 
  703.     super release.
  704.     self nilFields! !
  705.  
  706. !Mode methodsFor: 'display box access'!
  707.  
  708. computeDisplayBox
  709.     "This is for the use of the 'displayBox' method only.  Private!!   Shan 
  710.     April 17, 1989"
  711.  
  712.     self isTopView
  713.         ifTrue: [^self displayTransform: self getWindow]
  714.         ifFalse: [^superView insetDisplayBox intersect: (self displayTransform: self getWindow)]!
  715.  
  716. displayBox
  717.     "The definition of displayBox is still the same.  This method is override 
  718.       because the MMS has a different definition of insetDisplayBox than 
  719.       
  720.     Smalltalk.  As a consequence of changing the definition of   
  721.     insetDisplayBox and the method 'computeInsetDisplayBox', the   
  722.     displayBox computed here needs to be intersected with the   
  723.     insetDisplayBox of the superView."
  724.     " Shan - 10 December 1988"
  725.     "self isTopView  
  726.     ifTrue: [^self insetDisplayBox expandBy: self borderWidth]  
  727.     ifFalse: [^(self insetDisplayBox expandBy: self borderWidth)  
  728.     intersect: superView insetDisplayBox]"
  729.     "Optimized for displayBox access.  Now the instance variable  
  730.     'insetDisplayBox' actually stores the displayBox.  Shan April 17,  
  731.     1989"
  732.  
  733.     insetDisplayBox == nil ifTrue: [insetDisplayBox _ self computeDisplayBox].
  734.     ^insetDisplayBox!
  735.  
  736. insetDisplayBox
  737.     "The access of insetDisplayBox is sacrified to make the displayBox 
  738.     access faster.  Shan April 17, 1989"
  739.  
  740.     self isTopView
  741.         ifTrue: [^self unclippedDisplayBox insetBy: self borderWidth]
  742.         ifFalse: [^(self unclippedDisplayBox insetBy: self borderWidth)
  743.                 intersect: superView insetDisplayBox]!
  744.  
  745. recomputeDisplayBox
  746.     "This is for the mode to adjust its display box when something 
  747.     changes the box.  Used in the 'highlight' methods defined in Mode.  
  748.     Shan May 30, 1989"
  749.  
  750.     insetDisplayBox _ self computeDisplayBox!
  751.  
  752. setUnclippedDisplayBox: box 
  753.     "Change the displayBox.  This is also used to handle a resizable text   
  754.     (like the icon name in the Mac. finder.)   Shan April 23, 1989"
  755.  
  756.     | v aRect oldDispB |
  757.     oldDispB _ self displayBox.
  758.     v _ superView inverseDisplayTransform: box.
  759.     self window: (self window origin extent: v extent)
  760.         viewport: v.
  761.     self computeLayering.
  762.     (oldDispB intersects: box)
  763.         ifTrue: 
  764.             [aRect _ box merge: oldDispB.
  765.             superView computeSubLayeringBelow: self withIn: aRect]
  766.         ifFalse: 
  767.             [superView computeSubLayeringBelow: self withIn: oldDispB.
  768.             superView computeSubLayeringBelow: self withIn: box].
  769.     "For roaming.  Shan June 23, 1989"
  770.     superView changed: #contentsBoundingBoxMayBeChanged!
  771.  
  772. setUnclippedDisplayBoxExtent: extent 
  773.     "Change the displayBox extent.  This is used to handle a resizable 
  774.     text (like the icon name in the Mac. finder).   Shan April 12, 1989"
  775.  
  776.     | newDispBox |
  777.     newDispBox _ self unclippedDisplayBox extent: extent.
  778.     self setUnclippedDisplayBox: newDispBox!
  779.  
  780. setUnclippedDisplayBoxOrigin: origin 
  781.     "This is for moving the mode in absolute coordinate.  Shan April 23, 
  782.     1989 "
  783.  
  784.     | newDispBox |
  785.     newDispBox _ origin extent: self unclippedDisplayBox extent.
  786.     self setUnclippedDisplayBox: newDispBox!
  787.  
  788. unclippedDisplayBox
  789.     "The displayBox in Smalltalk is clipped to the insetDisplayBox of the 
  790.     superView.  This one returns an displayBox that is not clipped.  Shan 
  791.     March 19, 1989"
  792.  
  793.     ^self displayTransform: self getWindow! !
  794.  
  795. !Mode methodsFor: 'controller access'!
  796.  
  797. controller: aController 
  798.     "Shan June 11, 1989"
  799.  
  800.     self semanticObject: model controller: aController!
  801.  
  802. defaultControllerClass
  803.     ^MController!
  804.  
  805. semanticObject: aSemObj controller: aController 
  806.     "The order of the last two statments has been changed to   
  807.     avoid endless loop when a MMSController1 is assigned to the mode. 
  808.     June 11, 1989  Shan"
  809.     "Added, mode connection.  Shan April 12, 1989"
  810.  
  811.     model ~~ nil & (model ~~ aSemObj) ifTrue: [model removeDependent: self].
  812.     aSemObj ~~ nil & (aSemObj ~~ model)
  813.         ifTrue: 
  814.             [aSemObj addDependent: self.
  815.             "Make the link explicit.  Implicit dependency may not be a   
  816.             good idea.  We will see.  Shan April 12, 1989"
  817.             (aSemObj isKindOf: SemanticObject)
  818.                 ifTrue: [aSemObj mode: self]].
  819.     model _ aSemObj.
  820.     controller _ aController.
  821.     aController ~~ nil
  822.         ifTrue: 
  823.             [aController mode: self.
  824.             aController semanticObject: aSemObj]! !
  825.  
  826. !Mode methodsFor: 'event handling'!
  827.  
  828. interestedIn: event 
  829.     "This is the part of the event dispatching mechanism that decides 
  830.     whether the mode should process the event.  Shan March 23, 1989."
  831.  
  832.     ^visible and: [self containsPoint: event origin]!
  833.  
  834. processEvent: event 
  835.     (self interestedIn: event)
  836.         ifTrue: 
  837.             [subViews reverseDo: [:each | (each processEvent: event)
  838.                     ifTrue: [^true]].
  839.             "generate and proces the enter/leave mode events when self 
  840.             is the first mode to see the cursorMove event.  April 11, 
  841.             1989 "
  842.             event selector = #cursorMove & event enterLeaveUsed not
  843.                 ifTrue: 
  844.                     [self processEnterLeave: event.
  845.                     event enterLeaveUsed: true].
  846.             ^self controller processEvent: event]
  847.         ifFalse: [^false]! !
  848.  
  849. !Mode methodsFor: 'enter/leaveEvent-process'!
  850.  
  851. commonAncestor
  852.     "This will return the ancestor that contains both the current point 
  853.     and the previous point.  This is optimized by using the following tow 
  854.     facts.  First, since the cursorMove event got here, all the ancestors 
  855.     of the mode contains the origin of the event.  Second, the ancestor 
  856.     mode that contains the previous point must have the instance 
  857.     variable 'cursorIn' set to true."
  858.     "Shan Mrach 15, 1989"
  859.  
  860.     cursorIn
  861.         ifTrue: [^self]
  862.         ifFalse: [^superView commonAncestor]!
  863.  
  864. cursorIn
  865.     ^cursorIn!
  866.  
  867. processEnter: enterEvent 
  868.     "Ask all the modes, start from self, entered by the cursor process  
  869.     enterMode event.  Shan March 15, 1989"
  870.     "Be sure to propagate changes to the same method in PollingEnvMode. 
  871.      Shan July 18, 1989"
  872.  
  873.     | topSubView |
  874.     visible ifFalse: [^false].
  875.     "Shan June 13, 1989"
  876.     cursorIn _ true.
  877.     self controller processEvent: enterEvent.
  878.     topSubView _ self subViewContaining: enterEvent origin.
  879.     topSubView notNil ifTrue: [topSubView processEnter: enterEvent]!
  880.  
  881. processEnterLeave: event 
  882.     "I have got a cursorMove event, see if I need to generate enter/leave 
  883.        mode events and process them.  'event' is a cursorMove event."
  884.     "Shan March 15, 1989"
  885.  
  886.     | commonAncestor topSubModeLeft topSubModeEntered leaveEvent enterEvent temp|
  887. "Transcript show: 'p'."    commonAncestor _ self commonAncestor.
  888.     "If commonAncestor is self.  There is no enter/leave happened."
  889.     "self == commonAncestor ifTrue: [^self].  No!!!!!!  This won't work for  
  890.     the case where the cursor comes form a subMode of self.  Shan  
  891.     March 16, 1989"
  892.     "Search for the subMode that contains the previous cursor point.     
  893.     This is optimized by the fact that a mode contains the previous    
  894.     cursor point must have 'cursorIn' set to true."
  895.     topSubModeLeft _ commonAncestor topSubModeLeft.
  896.     topSubModeLeft notNil
  897.         ifTrue: 
  898.             ["construct the leaveMode event"
  899.              "Transcript show: ' ',(topSubModeLeft displayBox width printString)."
  900.             leaveEvent _ event copy.
  901.             temp _ leaveEvent origin.
  902.             leaveEvent origin: event previousOrigin.
  903.             leaveEvent previousOrigin: temp. "Used in MenuCell>cursorLeave:.  This point is not used to check who was left by the cursor now (replaced by using cursorIn), but is kept to make consistent that the origin of an event always corresponds to the place where it happens.  Shan July 19, 1989"
  904.             leaveEvent selector: #leaveMode.
  905.             "process it."
  906.             topSubModeLeft processLeave: leaveEvent].
  907.     "Search for the subMode that was entered by the cursor.  It should 
  908.     be a subMode of commonAncestor and an ancestor of self."
  909.     "topSubModeEntered _ commonAncestor subViewContaining: event 
  910.     origin. <--This is optimized by the 'topSubModeEnteredFrom:' method."
  911.     topSubModeEntered _ commonAncestor topSubModeEnteredFrom: self.
  912.     topSubModeEntered notNil
  913.         ifTrue: 
  914.             ["construct the enterMode event"
  915.             enterEvent _ event copy.
  916.             enterEvent selector: #enterMode.
  917.             "process it."
  918.             topSubModeEntered processEnter: enterEvent]!
  919.  
  920. processLeave: leaveEvent 
  921.     "Ask all the modes, start from self, left by the cursor to process   
  922.     leaveMode event."
  923.     "Shan March 15, 1989"
  924.  
  925.     | topSubView |
  926.     cursorIn _ false.
  927.     "The sequence here is significant.  cursorIn must be set to false when 
  928.     a window is closed even though the window has been set to invisible 
  929.     by erasing itself.  Shan July 19, 1989"
  930.     visible ifFalse: [^false].
  931.     "Shan June 13, 1989"
  932.     "topSubView _ self subViewContaining: leaveEvent origin."
  933.     topSubView _ subViews detect: [:each | each cursorIn] ifNone: [].
  934.     topSubView notNil ifTrue: [topSubView processLeave: leaveEvent].
  935.     self controller processEvent: leaveEvent!
  936.  
  937. topSubModeEnteredFrom: offspring 
  938.     "This is another optimization making use of the fact that the subMode 
  939.     sought is also an ancestor mode of the offspring."
  940.     "Shan Mrach 16, 1989"
  941.  
  942.     | dad child |
  943.     offspring == self ifTrue: [^nil].
  944.     child _ offspring.
  945.     dad _ child superView.
  946.     [dad ~~ self]
  947.         whileTrue: 
  948.             [child _ dad.
  949.             dad _ child superView].
  950.     ^child!
  951.  
  952. topSubModeLeft
  953.     "This will return the first subMode that the cursor left.  The subMode 
  954.     is the only subMode of self that has the 'cursorIn' set to true."
  955.     "Shan Mrach 15, 1989"
  956.  
  957.     subViews reverseDo: [:aSubView | aSubView cursorIn ifTrue: [^aSubView]].
  958.     ^nil! !
  959.  
  960. !Mode methodsFor: 'subMode insert/delete'!
  961.  
  962. addSubMode: aMode 
  963.     "Shan June 23, 1989"
  964.  
  965.     self addSubMode: aMode at: aMode viewport origin!
  966.  
  967. addSubMode: aMode absAt: aPoint 
  968.     "Shan August 1, 1989"
  969.  
  970.     self
  971.         addSubMode: aMode
  972.         at: (self inverseDisplayTransform: aPoint)!
  973.  
  974. addSubMode: aMode absAt: aPoint extent: ext 
  975.     "Shan August 1, 1989"
  976.  
  977.     self
  978.         addSubMode: aMode
  979.         at: (self inverseDisplayTransform: aPoint)
  980.         extent: ext!
  981.  
  982. addSubMode: aMode at: aPoint 
  983.     "Shan June 23, 1989"
  984.  
  985.     self addSubMode: aMode at: aPoint extent: aMode viewport extent!
  986.  
  987. addSubMode: aMode at: aPoint extent: ext 
  988.     "Add aMode with extent 'ext' to be the front most subMode of self    
  989.     at aPoint.  The viewport and the window are of the same size."
  990.     "Shan June 23, 1989"
  991.  
  992.     | aViewport |
  993.     aViewport _ aPoint extent: ext.
  994.     super
  995.         addSubView: aMode
  996.         window: (aMode window origin extent: ext)
  997.         viewport: aViewport.
  998.     aMode computeLayering.
  999.     aMode insideColor notNil ifTrue: ["A transparent mode (insideColor nil) does not affect the clipping of other modes.  Shan April 12, 1989"
  1000.         self computeSubLayeringBelow: aMode withIn: aMode displayBox].
  1001.     "For roaming.  Shan June 23, 1989"
  1002.     self changed: #contentsBoundingBoxMayBeChanged!
  1003.  
  1004. addSubMode: aMode in: aRelativeRectangle 
  1005.     "Add aMode to be the front most subMode of self."
  1006.     "Shan March 17, 1989"
  1007.  
  1008.     | subViewPort subWindow myWindow myExtent myOrigin |
  1009.     self error: 'Not supported.'.
  1010.     self addSubView: aMode ifCyclic: [self error: 'cycle in subView structure.'].
  1011.     myWindow _ self window.
  1012.     myExtent _ myWindow extent.
  1013.     myOrigin _ myWindow origin.
  1014.     subViewPort _ myExtent * aRelativeRectangle origin + myOrigin corner: myExtent * aRelativeRectangle corner + myOrigin.
  1015.     "Added to keep the size of the window and viewport match.  Shan 
  1016.     March 23, 1989"
  1017.     subWindow _ aMode window origin extent: myExtent * aRelativeRectangle extent.
  1018.     aMode window: subWindow viewport: subViewPort.
  1019.     self computeSubLayering!
  1020.  
  1021. addToBackSubMode: aMode 
  1022.     "Add aMode to be the back most subMode of self.  Shan June 23, 
  1023.     1989 "
  1024.  
  1025.     self addToBackSubMode: aMode at: aMode viewport origin!
  1026.  
  1027. addToBackSubMode: aMode at: aPoint 
  1028.     "Shan June 23, 1989"
  1029.  
  1030.     self addToBackSubMode: aMode at: aPoint extent: aMode viewport extent!
  1031.  
  1032. addToBackSubMode: aMode at: aPoint extent: ext 
  1033.     "Add aMode with extent 'ext' to be the front most subMode of self    
  1034.     at aPoint.  The viewport and the window are of the same size."
  1035.     "Shan June 23, 1989"
  1036.  
  1037.     | aViewport |
  1038.     aViewport _ aPoint extent: ext.
  1039.     self
  1040.         addToBackSubMode: aMode
  1041.         window: (aMode window origin extent: ext)
  1042.         viewport: aViewport.
  1043.     aMode computeLayering.
  1044.     aMode insideColor notNil ifTrue: ["A transparent mode (insideColor nil) does not affect the clipping of other modes.  Shan April 12, 1989"
  1045.         self computeSubLayeringBelow: aMode withIn: aMode displayBox].
  1046.     "For roaming.  Shan June 23, 1989"
  1047.     self changed: #contentsBoundingBoxMayBeChanged!
  1048.  
  1049. addToBackSubMode: aMode window: aWindow viewport: aViewport
  1050.     "Shan June 23, 1989"
  1051.  
  1052.     (self isCyclic: aMode)
  1053.         ifTrue: [self error: 'cycle in subView structure.']
  1054.         ifFalse: 
  1055.             [aMode removeFromSuperView.
  1056.             subViews addFirst: aMode.
  1057.             aMode superView: self].    
  1058.     aMode window: aWindow viewport: aViewport!
  1059.  
  1060. removeFromSuperMode
  1061.     "Shan September 16, 1989"
  1062.  
  1063.     superView ~= nil ifTrue: [superView removeSubMode: self]!
  1064.  
  1065. removeSubMode: aMode 
  1066.     "Remove aMode from the subModes."
  1067.     "Shan June 23, 1989"
  1068.  
  1069.     | dispB |
  1070.     dispB _ aMode displayBox.
  1071.     aMode unMap.
  1072.     self computeSubLayeringBelow: aMode withIn: dispB.
  1073.     super removeSubView: aMode.
  1074.     aMode map.
  1075.     "For roaming.  Shan June 23, 1989"
  1076.     self changed: #contentsBoundingBoxMayBeChanged! !
  1077.  
  1078. !Mode methodsFor: 'visibility'!
  1079.  
  1080. isVisible
  1081.     "This is not changed to be recursively searching the mode hierarchy because sometimes it is desirable to display a mode even it is not visible on screen.  e.g. buffering it into a form.  Shan July 21, 1989"
  1082.  
  1083.     ^visible! !
  1084.  
  1085. !Mode methodsFor: 'bordering'!
  1086.  
  1087. borderColor
  1088.     ^dispObj borderColor!
  1089.  
  1090. borderColor: aColor 
  1091.     dispObj borderColor: aColor!
  1092.  
  1093. borderWidth
  1094.     ^dispObj borderWidth!
  1095.  
  1096. borderWidth: aWidth 
  1097.     dispObj borderWidth: aWidth!
  1098.  
  1099. insideColor
  1100.     ^dispObj insideColor!
  1101.  
  1102. insideColor: aColor 
  1103.     | previousColor |
  1104.     previousColor _ dispObj insideColor.
  1105.     dispObj insideColor: aColor.
  1106.     "Changing the inside color from nil to something makes the transparent 
  1107.      window opaque. Recompute the layering.  Shan April 12, 1989"
  1108.     previousColor isNil & aColor notNil & superView notNil ifTrue: [superView computeSubLayeringBelow: self withIn: self displayBox]! !
  1109.  
  1110. !Mode methodsFor: 'buffering'!
  1111.  
  1112. absoluteBufferSubViews
  1113.     subViews do: [:each| each displayObject makeAbsoluteFaster]!
  1114.  
  1115. image
  1116.     "Returns a form that stores the image of me and my subModes at the 
  1117.     current size."
  1118.     " Shan April 23, 1989"
  1119.  
  1120.     ^self imageSize: nil window: nil!
  1121.  
  1122. imageSize: aPoint 
  1123.     "Shan August 27, 1989"
  1124.  
  1125.     ^self imageSize: aPoint window: nil!
  1126.  
  1127. imageSize: aPoint window: aWindow 
  1128.     "This is specifically for the window buffering mechanism.  Returns a  
  1129.     form of size aPoint that stores the image of the things in me in 
  1130.     aWindow.  When aPoint is nil, current unclippedDispBox extent is used 
  1131.     as a default.  When aWidow is nil, current window is used."
  1132.     " Shan April 6, 1989"
  1133.  
  1134.     | f |
  1135.     f _ self shallowCopy privateGetImageSize: aPoint window: aWindow.
  1136.     subViews do: [:each | each superView: self].
  1137.     "Change it back."
  1138.     self unlock.
  1139.     self computeLayering.
  1140.     ^f!
  1141.  
  1142. privateGetImageSize: ext window: aWindow 
  1143.     "This is specifically for the window buffering mechanism.  Returns a 
  1144.     form that stores the image of me and my subModes.  When ext is nil, 
  1145.     current extent of the unclippedDispBox will be used.  If aWindow is 
  1146.     nil, current window size is used. The stuff here is fairly complicated.  
  1147.     Self must be a proxy.  Warning!!  No other use allowed."
  1148.     " Shan April 6, 1989"
  1149.  
  1150.     | form  dispExt dispWind |
  1151.     subViews do: [:each | each superView: self]. "Redirect the pointers."
  1152.     "Set up the form."
  1153.     
  1154.     ext isNil
  1155.         ifTrue: [dispExt _ self unclippedDisplayBox extent] ifFalse: [dispExt _ ext].
  1156.     self insideColor notNil ifTrue: [    form _ Form extent: dispExt]
  1157. ifFalse: [form _ MMSOpaqueForm figure: (Form extent: dispExt)
  1158.                         shape: ((Form extent: dispExt)
  1159.                                 fill: (0 @ 0 extent: dispExt)
  1160.                                 rule: Form over
  1161.                                 mask: Form white)].
  1162.     aWindow isNil ifTrue:[dispWind _ self window] ifFalse: [dispWind _ aWindow].
  1163.     "Make self the topView and un-obscured."
  1164.     "savedScale _ displayTransformation scale." "Save the scale"
  1165.     superView _ nil. "Make to the top."
  1166.     self unlock. "So that subModes have a chance to recompute their dispBox."
  1167.     self window: dispWind viewport: (0@0 extent: dispExt).
  1168.     "transformation _ WindowingTransformation scale: savedScale translation: ((0 @ 0)-self window origin)."
  1169.     obscuringRects _ OrderedCollection new: 0.
  1170.     "Make me un-obscured"
  1171.     self computeLayering.
  1172.     visible _ true. 
  1173.     self displayOn: form in: nil.
  1174.     "self insideColor notNil ifTrue: [^form]
  1175.         ifFalse: [^OpaqueForm shape: form]" 
  1176. ^form!
  1177.  
  1178. smartBufferSubViews
  1179.     subViews do: [:each| each displayObject makeFaster]! !
  1180.  
  1181. !Mode methodsFor: 'sharedStyle-highlight'!
  1182.  
  1183. colorBorderHighlight
  1184.     "This is a shared style of highlight.  Shan May 29, 1989"
  1185.  
  1186.     dispObj borderColorTemp: Form black.
  1187.     self displayBorder!
  1188.  
  1189. colorBorderHighlightN
  1190.     "This is a shared style of highlight.  Shan May 29, 1989"
  1191.  
  1192.     dispObj borderColorTemp: Form gray.
  1193.     self displayBorder!
  1194.  
  1195. inverseHighlight
  1196.     "This is a shared style of highlight.  Shan May 29, 1989"
  1197.  
  1198.     dispObj inverse: self unclippedDisplayBox extent.
  1199.     self display!
  1200.  
  1201. inverseHighlightN
  1202.     "This is a shared style of deHighlight.  Shan May 29, 1989"
  1203.  
  1204.     dispObj inverse.
  1205.     self display!
  1206.  
  1207. thickBorderHighlight
  1208.     "This is a shared style of highlight.  Shan May 29, 1989"
  1209.  
  1210.     dispObj borderWidthTemp: dispObj borderWidth *2.
  1211.     self display!
  1212.  
  1213. thickBorderHighlightN
  1214.     "This is a shared style of highlight.  Shan May 29, 1989"
  1215.  
  1216.     dispObj borderWidthTemp: dispObj borderWidth / 2.
  1217.     self display! !
  1218.  
  1219. !Mode methodsFor: 'indicating'!
  1220.  
  1221. deHighlight
  1222.     "Shan May 29, 1989"
  1223.  
  1224.     | temp diffSize |
  1225.     highlighted ifFalse: [^self].
  1226.     highlightDispObj isNil ifTrue: [^self].
  1227.     highlighted _ false.
  1228.     (highlightDispObj isKindOf: MDisplayObject)
  1229.         ifTrue: 
  1230.             [(dispObj isKindOf: AnimationDispObj)
  1231.                 ifTrue: [dispObj stopDisplayLoop].
  1232.             "Exchange dispObj and the highlightDispObj."
  1233.             dispObj insideColor isNil | (diffSize _ dispObj boundingBox ~= highlightDispObj boundingBox) ifTrue: [self erase].
  1234.             temp _ dispObj.
  1235.             dispObj _ highlightDispObj.
  1236.             highlightDispObj _ temp.
  1237.             diffSize ifTrue: [self recomputeDisplayBox].
  1238.             ^self display]
  1239.         ifFalse: ["A shared style.  We have to use a convention here.  The     
  1240.             deHighlight selector is the highlight selector with an 'N'     
  1241.             (negate) at the end.  Shan May 29, 1989"
  1242.             ^self perform: (highlightDispObj asString , 'N') asSymbol]!
  1243.  
  1244. highlight
  1245.     "The highlight business is originally not the responsibility of mode.  
  1246.     Mode should not care about the appearance of it.  The reason it is 
  1247.     here is because it is so oftenly used.  The inst var. 'highlightDispObj' 
  1248.     stores 2 kinds of object.   A DispObj indicates that it is the 
  1249.     appearance of the mode when highlighted.  A symbol means that a 
  1250.     shared style of highlight is used.  Those shared styles are 
  1251.     implemented in the Mode class.  This is similar to the implementation 
  1252.     of MMSController1.  Shan May 29, 1989"
  1253.  
  1254.     | temp diffSize |
  1255.     highlighted ifTrue: [^self].
  1256.     highlightDispObj isNil ifTrue: [^self].
  1257.     highlighted _ true.
  1258.     (highlightDispObj isKindOf: MDisplayObject)
  1259.         ifTrue: 
  1260.             ["Exchange dispObj and the highlightDispObj."
  1261.             highlightDispObj insideColor isNil | (diffSize _ dispObj boundingBox ~= highlightDispObj boundingBox) ifTrue: [self erase].
  1262.             temp _ dispObj.
  1263.             dispObj _ highlightDispObj.
  1264.             highlightDispObj _ temp.
  1265.             diffSize ifTrue: [self recomputeDisplayBox]. 
  1266.             ^self display]
  1267.         ifFalse: ["A shared style.  Send message to self to perform it.  The       
  1268.             highlightDispObj actually stores a symbol which will be used   
  1269.                 as a message selector."
  1270.             ^self perform: highlightDispObj]!
  1271.  
  1272. highlightDispObj
  1273.     "Shan May 29, 1989"
  1274.  
  1275.     ^highlightDispObj!
  1276.  
  1277. highlightDispObj: d
  1278.     "Shan May 29, 1989"
  1279.  
  1280.     highlightDispObj _ d!
  1281.  
  1282. highlighted
  1283.     "Shan July 23, 1989"
  1284.  
  1285.     ^highlighted! !
  1286.  
  1287. !Mode methodsFor: 'sizing'!
  1288.  
  1289. corner
  1290.     "Shan 31 May 1990"
  1291.  
  1292.     ^self origin + self extent!
  1293.  
  1294. edit
  1295.     "This will bring up an edit session similar to MacDraw.  Shan June 13, 
  1296.     1989 "
  1297.     "Original was editSizeAndPosition.  Add the ability to edit other attributes
  1298.     of the mode.  Shan July 30, 1989"
  1299.  
  1300.     | bkMode proxy dot |
  1301.     bkMode _ (ModeEditBackground on: self) mode.
  1302.     bkMode extent: self topMode window extent.
  1303.     self topMode addSubMode: bkMode.
  1304.     proxy _ ModeEditProxy on: self.
  1305.     self addDependent: proxy.
  1306.     bkMode addSubMode: proxy mode.
  1307.     dot _ ResizeDot on: self withMessage: #topLeft.
  1308.     self addDependent: dot.
  1309.     bkMode addSubMode: dot mode.
  1310.     dot _ ResizeDot on: self withMessage: #topCenter.
  1311.     self addDependent: dot.
  1312.     bkMode addSubMode: dot mode.
  1313.     dot _ ResizeDot on: self withMessage: #topRight.
  1314.     self addDependent: dot.
  1315.     bkMode addSubMode: dot mode.
  1316.     dot _ ResizeDot on: self withMessage: #bottomLeft.
  1317.     self addDependent: dot.
  1318.     bkMode addSubMode: dot mode.
  1319.     dot _ ResizeDot on: self withMessage: #bottomCenter.
  1320.     self addDependent: dot.
  1321.     bkMode addSubMode: dot mode.
  1322.     dot _ ResizeDot on: self withMessage: #bottomRight.
  1323.     self addDependent: dot.
  1324.     bkMode addSubMode: dot mode.
  1325.     dot _ ResizeDot on: self withMessage: #leftCenter.
  1326.     self addDependent: dot.
  1327.     bkMode addSubMode: dot mode.
  1328.     dot _ ResizeDot on: self withMessage: #rightCenter.
  1329.     self addDependent: dot.
  1330.     bkMode addSubMode: dot mode.
  1331.     "This is for the inversion of dots.  The mode will not response to the 
  1332.     'leaveMode' event and change its appearance after the resizeDots 
  1333.     are drawn.  Shan June 14, 1989"
  1334.     "visible _ false.  Shan September 18, 1989"
  1335.     cursorIn _ false.
  1336.     self changed: #moveResized!
  1337.  
  1338. extent
  1339.     "Shan July 25, 1989"
  1340.  
  1341.     ^self viewport extent!
  1342.  
  1343. extent: extent 
  1344.     "Shan June 6,1989"
  1345.  
  1346.     self window: (self window origin extent: extent)
  1347.         viewport: (self viewport origin extent: extent)!
  1348.  
  1349. height: h 
  1350.     "Shan July 25, 1989"
  1351.  
  1352.     self extent: (self extent y: h)!
  1353.  
  1354. origin
  1355.     "Shan July 25, 1989"
  1356.  
  1357.     ^self viewport origin!
  1358.  
  1359. origin: origin 
  1360.     "Shan June 16,1989"
  1361.  
  1362.     self window: self window
  1363.         viewport: (origin extent: self window extent)!
  1364.  
  1365. origin: origin extent: extent 
  1366.     "This forces my window and viewport to be of the same size."
  1367.     "Shan June 16,1989"
  1368.  
  1369.     self window: (self window origin extent: extent)
  1370.         viewport: (origin extent: extent)!
  1371.  
  1372. resizeStyle
  1373.     ^ resizeStyle!
  1374.  
  1375. resizeStyle: s 
  1376.     "Shan June 8, 1989"
  1377.  
  1378.     resizeStyle _ s!
  1379.  
  1380. superModeWindowChangedFrom: oldW to: newW 
  1381.     "This is for the superMode to notify subModes that it has been
  1382.     resized.  Shan June 8, 1989"
  1383.  
  1384.     | newVp vp dist |
  1385.     resizeStyle isNil ifTrue: ["Default.  My viewport will stay the same."
  1386.         ^self].
  1387.     "The recursion continues by setting the window of self which will 
  1388.     trigger the 'superModeWindowChangedFrom: to:' method in subModes."
  1389.     vp _ self viewport.
  1390.     newVp _ vp deepCopy.
  1391.     resizeStyle extentX == #fixed
  1392.         ifTrue: [resizeStyle originX == #fixed
  1393.                 ifTrue: 
  1394.                     ["shrinkBox"
  1395.                     newVp left: vp left.
  1396.                     newVp width: vp width]
  1397.                 ifFalse: [resizeStyle cornerX == #fixed
  1398.                         ifTrue: 
  1399.                             ["resizeBox"
  1400.                             dist _ oldW width - vp right.
  1401.                             newVp right: newW width - dist.
  1402.                             newVp left: newVp right - vp width]
  1403.                         ifFalse: 
  1404.                             ["Titlebar text.  Stretch both distances to left  
  1405.                             and right but keep the ext"
  1406.                             newVp left: (vp left * (newW width - vp width) / (oldW width - vp width)) rounded.
  1407.                             newVp width: vp width]]]
  1408.         ifFalse: [resizeStyle originX == #fixed
  1409.                 ifTrue: [resizeStyle cornerX == #fixed
  1410.                         ifTrue: 
  1411.                             ["Application mode."
  1412.                             newVp left: vp left.
  1413.                             newVp right: vp right + (newW width - oldW width)]
  1414.                         ifFalse: 
  1415.                             ["Only left is fixed."
  1416.                             newVp left: vp left.
  1417.                             newVp width: (vp width * (newW width - vp left) / (oldW width - vp left)) rounded]]
  1418.                 ifFalse: [resizeStyle cornerX == #fixed
  1419.                         ifTrue: 
  1420.                             ["Only distance to the right is fixed."
  1421.                             dist _ oldW width - vp right.
  1422.                             newVp right: newW width - dist.
  1423.                             "Shan November 21, 1989 newVp left: (newVp right * (newW width - dist) / (oldW width - dist)) rounded"
  1424.                             newVp left: (newVp right * (vp left) / (vp right)) rounded]]].
  1425.     resizeStyle extentY == #fixed
  1426.         ifTrue: [resizeStyle originY == #fixed
  1427.                 ifTrue: 
  1428.                     ["shrinkBox"
  1429.                     newVp top: vp top.
  1430.                     newVp height: vp height]
  1431.                 ifFalse: [resizeStyle cornerY == #fixed
  1432.                         ifTrue: 
  1433.                             ["resizeBox"
  1434.                             dist _ oldW height - vp bottom.
  1435.                             newVp bottom: newW height - dist.
  1436.                             newVp top: newVp bottom - vp height]
  1437.                         ifFalse: 
  1438.                             ["Stretch both distances to top and bottom but 
  1439.                              keep the ext"
  1440.                             newVp top: (vp top * (newW height - vp height) / (oldW height - vp height)) rounded.
  1441.                             newVp height: vp height]]]
  1442.         ifFalse: [resizeStyle originY == #fixed
  1443.                 ifTrue: [resizeStyle cornerY == #fixed
  1444.                         ifTrue: 
  1445.                             ["Application mode."
  1446.                             newVp top: vp top.
  1447.                             newVp bottom: vp bottom + (newW height - oldW height)]
  1448.                         ifFalse: 
  1449.                             ["Only top is fixed."
  1450.                             newVp top: vp top.
  1451.                             newVp height: (vp height * (newW height - vp top) / (oldW height - vp top)) rounded]]
  1452.                 ifFalse: [resizeStyle cornerY == #fixed
  1453.                         ifTrue: 
  1454.                             ["Only distance to the bottom is fixed."
  1455.                             dist _ oldW height - vp bottom.
  1456.                             newVp bottom: newW height - dist.
  1457.                             "Shan November 21, 1989 newVp top: (newVp bottom * (newW height - dist) / (oldW height - dist)) rounded"
  1458.                             newVp top: (newVp bottom * (vp top) / (vp bottom)) rounded]]].
  1459.     newVp ~= vp ifTrue: [resizeStyle matchViewportWindow
  1460.         ifTrue: [self window: (self window origin extent: newVp extent)
  1461.                 viewport: newVp]
  1462.         ifFalse: [self window: self window viewport: newVp]]!
  1463.  
  1464. width: w 
  1465.     "Shan July 25, 1989"
  1466.  
  1467.     self extent: (self extent x: w)!
  1468.  
  1469. windowChangedFrom: oldW to: newW 
  1470.     "Need to inform the subModes.  The message is used by the method 
  1471.     'setWindow:'.  Shan June 9, 1989"
  1472.  
  1473.     subViews do: [:each | each superModeWindowChangedFrom: oldW to: newW]! !
  1474.  
  1475. !Mode methodsFor: 'private'!
  1476.  
  1477. checkResize: aWindow 
  1478.     "Shan March 20, 1990"
  1479.  
  1480.     (window notNil and: [window ~= aWindow])
  1481.         ifTrue: [self windowChangedFrom: self window to: aWindow]!
  1482.  
  1483. clearCursorIn
  1484.     "Shan July 28, 1989"
  1485.  
  1486.     cursorIn _ false.
  1487.     subViews notNil ifTrue: [subViews do: [:each | each clearCursorIn]]!
  1488.  
  1489. setVisible: aBool 
  1490.     "This also recompute the layering of the affected modes.  Shan March 
  1491.      19, 1989"
  1492.  
  1493.     visible ~= aBool
  1494.         ifTrue: 
  1495.             [visible _ aBool.
  1496.             superView notNil ifTrue: [superView computeSubLayeringBelow: self withIn: self displayBox]]!
  1497.  
  1498. setWindow: aWindow 
  1499.     "Override to insert the resizing handling functions.  The added    
  1500.     message is placed in front of the 'setWindow:' method to avoid losing 
  1501.     the viewport of the subModes that will be niled by the 'unluck'    
  1502.     message in the 'setWindow:' method.  Shan June 9, 1989"
  1503.  
  1504.     self checkResize: aWindow.
  1505.     super setWindow: aWindow! !
  1506.  
  1507. !Mode methodsFor: 'semObj access'!
  1508.  
  1509. semanticObject
  1510.     "Shan June 11, 1989"
  1511.     ^model!
  1512.  
  1513. semanticObject: aSemObj
  1514.     "Shan June 11, 1989"
  1515.  
  1516.     self semanticObject: aSemObj controller: controller! !
  1517.  
  1518. !Mode methodsFor: 'copying'!
  1519.  
  1520. deepCopy
  1521.     "Check self against the OccurrenceDictionary.  This method is 
  1522.     overriden in the Mode, MMSController1, SemanticObject and DispObj 
  1523.     class.  Shan  August 3, 1989"
  1524.  
  1525.     | newObject class index exist |
  1526.     exist _ true.
  1527.     newObject _ OccurrenceDictionary at: self ifAbsent: [exist _ false].
  1528.     exist ifFalse: 
  1529.             [class _ self class.
  1530.             class == Object ifTrue: [^self].
  1531.             class isVariable
  1532.                 ifTrue: 
  1533.                     [index _ self basicSize.
  1534.                     newObject _ class basicNew: index.
  1535.                     OccurrenceDictionary at: self put: newObject.
  1536.                     [index > 0]
  1537.                         whileTrue: 
  1538.                             [newObject basicAt: index put: (self basicAt: index) deepCopy.
  1539.                             index _ index - 1]]
  1540.                 ifFalse: 
  1541.                     [newObject _ class basicNew.
  1542.                     OccurrenceDictionary at: self put: newObject].
  1543.             index _ class instSize.
  1544.             [index > 0]
  1545.                 whileTrue: 
  1546.                     [newObject instVarAt: index put: (self instVarAt: index) deepCopy.
  1547.                     index _ index - 1]].
  1548.     ^newObject!
  1549.  
  1550. duplicate
  1551.     "This is to replace deepCopy which does not handle the pointer loop  
  1552.     well.  Shan August 3, 1989"
  1553.  
  1554.     | duplicate  temp |
  1555.     OccurrenceDictionary isEmpty not ifTrue: [OccurrenceDictionary _ IdentityDictionary new].
  1556.     "Avoid copying the superView"
  1557.     temp _ superView.
  1558.     superView _ nil.
  1559.     duplicate _ self deepCopy.
  1560.     superView _ temp.
  1561.     OccurrenceDictionary _ IdentityDictionary new.
  1562.     ^duplicate! !
  1563.  
  1564. !Mode methodsFor: 'tracking/replay'!
  1565.  
  1566. eventQueue
  1567.     "Shan 13 July 1990"
  1568.  
  1569.     ^self superMode eventQueue! !
  1570. "-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- "!
  1571.  
  1572. Mode class
  1573.     instanceVariableNames: ''!
  1574.  
  1575.  
  1576. !Mode class methodsFor: 'initialization'!
  1577.  
  1578. initialize
  1579.     "To support the new deepCopy.  Shan August 3, 1989"
  1580.  
  1581.     Smalltalk at: #OccurrenceDictionary put: IdentityDictionary new! !
  1582.  
  1583. !Mode class methodsFor: 'layer manip. tests'!
  1584.  
  1585. moveTest1
  1586.     "Test the 'moveTo:' method"
  1587.     "Shan - March 17 1989"
  1588.     "Mode moveTest1"
  1589.  
  1590.     | v sb1 sb2 |
  1591.     v _ RootMode origin: 10@10 extent: 200@200.
  1592.     v borderWidth: 4; borderColor: Form lightGray.
  1593.     v insideColor: Form white.
  1594.  
  1595.     sb1 _ Mode extent: 80@80.
  1596.     sb1 borderWidth: 2.
  1597.     sb1 insideColor: Form gray.
  1598.     v addSubMode: sb1 at: 50@50.
  1599.  
  1600.     sb2 _ Mode origin: 100@100 extent: 200@200.
  1601.     sb2 insideColor: Form veryLightGray.
  1602.     sb2 borderWidth: 3.
  1603.     v addSubMode: sb2.
  1604.  
  1605.     v display.
  1606.     
  1607.     sb1 moveTo: 10@10.
  1608.     Sensor waitClickButton.
  1609.     v display.
  1610.     sb2 moveTo: 30@30.
  1611.     Sensor waitClickButton.
  1612.     v display! !
  1613.  
  1614. !Mode class methodsFor: 'buffering test'!
  1615.  
  1616. bufferingTest
  1617.     "Test the ability to store a Mode on a form.  After the buffering the 
  1618.     mode should not be changed in any respect.  Shan April 6,1989"
  1619.     "Mode bufferingTest"
  1620.  
  1621.     | v sb1 sb2 |
  1622.     v _ RootMode origin: 250 @ 10 extent: 200 @ 200.
  1623.     v borderWidth: 4; borderColor: Form lightGray.
  1624.     v insideColor: Form white.
  1625.     sb1 _ Mode extent: 80 @ 80.
  1626.     sb1 borderWidth: 2.
  1627.     sb1 insideColor: Form gray.
  1628.     v addSubMode: sb1 at: 50 @ 50.
  1629.     sb2 _ Mode origin: 100 @ 100 extent: 200 @ 200.
  1630.     sb2 insideColor: Form veryLightGray.
  1631.     sb2 borderWidth: 3.
  1632.     v addSubMode: sb2.
  1633.     sb1 image display.
  1634.     v image displayAt: 0 @ 200.
  1635.     v display!
  1636.  
  1637. roamingTest
  1638.     "Test the ability to store a Mode on a form.  After the buffering the  
  1639.     mode should not be changed in any respect.  Shan April 6,1989"
  1640.     "Mode roamingTest"
  1641.  
  1642.     | v sb1 sb2 |
  1643.     v _ RootMode origin: 250 @ 10 extent: 200 @ 200.
  1644.     v borderWidth: 4; borderColor: Form lightGray.
  1645.     v insideColor: Form white.
  1646.     sb1 _ Mode extent: 80 @ 80.
  1647.     sb1 borderWidth: 2.
  1648.     sb1 insideColor: Form gray.
  1649.     v addSubMode: sb1 at: 50 @ 50.
  1650.     sb2 _ Mode origin: 100 @ 100 extent: 200 @ 200.
  1651.     sb2 insideColor: Form veryLightGray.
  1652.     sb2 borderWidth: 3.
  1653.     v addSubMode: sb2.
  1654.     (v imageSize: 100 @ 100 window: nil) display.
  1655.     (v imageSize: 100 @ 100 window: (25@25 extent: 200@200)) displayAt: 0@100.
  1656.     (v imageSize: 100 @ 100 window: (25@25 extent: 300@300)) displayAt: 0@200.
  1657.     v display! !
  1658.  
  1659. !Mode class methodsFor: 'basic tests'!
  1660.  
  1661. eraseTest
  1662.     "See if the mode erases correctly.  This also test the mouse query methods in EventQueue."
  1663.     "Shan - March 18 1989"
  1664.     "Mode eraseTest"
  1665.  
  1666.     | v sb1 sb2 |
  1667.     v _ RootMode origin: 250@10 extent: 200@200.
  1668.     v borderWidth: 4; borderColor: Form lightGray.
  1669.     v insideColor: Form white.
  1670.  
  1671.     sb1 _ Mode extent: 80@80.
  1672.     sb1 borderWidth: 2.
  1673.     sb1 insideColor: Form gray.
  1674.     v addSubMode: sb1 at: 50@50.
  1675.  
  1676.     sb2 _ Mode origin: 100@100 extent: 200@200.
  1677.     sb2 insideColor: Form veryLightGray.
  1678.     sb2 borderWidth: 3.
  1679.     v addSubMode: sb2.
  1680.  
  1681.     v display.
  1682.     EventQ enable.
  1683.     EventQ waitClickButton.
  1684.     EventQ disable. 
  1685.     sb2 erase!
  1686.  
  1687. highlightTest
  1688.     "Shan July 25, 1989"
  1689.     "self highlightTest"
  1690.  
  1691.     | m |
  1692.     m _ RootMode new.
  1693.     m highlightDispObj: #inverseHighlight.
  1694.     m displayObject relAdd: 'string' asDisplayText.
  1695.     m display.
  1696.     m inspect!
  1697.  
  1698. test11
  1699.     "Use the new creation method."
  1700.     "Shan - March 17 1989"
  1701.     "Mode test11"
  1702.  
  1703.     | v |
  1704.     v _ RootMode origin: 10@10 extent: 200@200.
  1705.     v borderWidth: 2.
  1706.     v insideColor: Form white.
  1707.     v display!
  1708.  
  1709. test2
  1710.     "Draw a white view with black border."
  1711.     "Add two subViews in it."
  1712.     "This is a test for the border management."
  1713.     " Shan - 10 December 1988"
  1714.     "Mode test2"
  1715.  
  1716.     | v sb1 sb2 |
  1717.     v _ RootMode new.
  1718.     v borderWidth: 4; borderColor: Form lightGray.
  1719.     v insideColor: Form white.
  1720.     v window: (0@0 extent: 200@200) viewport: (10@10 extent: 200@200).
  1721.  
  1722.     sb1 _ Mode new.
  1723.     sb1 window: (0@0 extent: 80@80) viewport: (50@50 extent: 80@80).
  1724.     sb1 borderWidth: 2.
  1725.     sb1 insideColor: Form gray.
  1726.     v addSubView: sb1.
  1727.  
  1728.     sb2 _ Mode new.
  1729.     sb2 window: (0@0 extent: 200@200) viewport: (100@100 extent: 200@200).
  1730.     sb2 insideColor: Form veryLightGray.
  1731.     sb2 borderWidth: 3.
  1732.     v addSubView: sb2.
  1733.  
  1734.     v computeLayering.
  1735.     v display!
  1736.  
  1737. test21
  1738.     "This should generate the same result as the test2."
  1739.     "Use the new creation method.  And attachment methods"
  1740.     "Shan - March 17 1989"
  1741.     "Mode test21"
  1742.  
  1743.     | v sb1 sb2 |
  1744.     v _ RootMode origin: 250@10 extent: 200@200.
  1745.     v borderWidth: 4; borderColor: Form lightGray.
  1746.     v insideColor: Form white.
  1747.  
  1748.     sb1 _ Mode extent: 80@80.
  1749.     sb1 borderWidth: 2.
  1750.     sb1 insideColor: Form gray.
  1751.     v addSubMode: sb1 at: 50@50.
  1752.  
  1753.     sb2 _ Mode origin: 100@100 extent: 200@200.
  1754.     sb2 insideColor: Form veryLightGray.
  1755.     sb2 borderWidth: 3.
  1756.     v addSubMode: sb2.
  1757.  
  1758.     v display!
  1759.  
  1760. test3
  1761.     "This is a test for the optimization that prevents totally invisible views being processed.  Notice that the clipping is also done here.  The purpose is to cut down the recursion in the method of 'display'."
  1762.     "There should only be 3 'self halt' executed.  The one for su11 should be clipped.  To test, uncomment the 'self halt' message in the 'display' method and run the test."
  1763.     " Shan - 10 December 1988"
  1764.     "Mode test3"
  1765.  
  1766.     | v sb1 sb11 sb2 |
  1767.     v _ RootMode new.
  1768.     v borderWidth: 4; borderColor: Form lightGray.
  1769.     v insideColor: Form white.
  1770.     v window: (0@0 extent: 200@200) viewport: (10@10 extent: 200@200).
  1771.  
  1772.     sb1 _ Mode new.
  1773.     sb1 window: (0@0 extent: 100@100) viewport: (25@25 extent: 100@100).
  1774.     sb1 borderWidth: 2.
  1775.     sb1 insideColor: Form gray.
  1776.  
  1777.     sb11 _ Mode new.
  1778.     sb11 window: (0@0 extent: 10@10) viewport: (25@25 extent: 10@10).
  1779.     sb11 borderWidth: 2.
  1780.     sb11 insideColor: Form darkGray.
  1781.     sb1 addSubView: sb11.
  1782.  
  1783.     sb2 _ Mode new.
  1784.     sb2 window: (0@0 extent: 180@180) viewport: (9@9 extent: 180@180).
  1785.     sb2 insideColor: Form veryLightGray.
  1786.     sb2 borderWidth: 3.
  1787.  
  1788.     v addSubView: sb1.
  1789.     v addSubView: sb2.    
  1790.  
  1791.     v computeLayering.
  1792.     v display! !
  1793.  
  1794. !Mode class methodsFor: 'instance creation'!
  1795.  
  1796. extent: extent 
  1797.     "This creates a Mode with its window and viewport of the same size."
  1798.     "Shan June 6,1989"
  1799.  
  1800.     ^self new extent: extent!
  1801.  
  1802. origin: origin 
  1803.     "This creates a Mode with its window and viewport of the same size."
  1804.     "Shan June 6,1989"
  1805.  
  1806.     ^self new origin: origin!
  1807.  
  1808. origin: origin extent: extent 
  1809.     "This creates a Mode with its window and viewport of the same size."
  1810.     "Shan March 17,1989"
  1811.  
  1812.     ^self new origin: origin extent: extent! !
  1813.  
  1814. Mode initialize!
  1815.  
  1816.  
  1817. Mode subclass: #ExpandedMode
  1818.     instanceVariableNames: 'painter '
  1819.     classVariableNames: ''
  1820.     poolDictionaries: ''
  1821.     category: 'Modes-Shan'!
  1822. ExpandedMode comment:
  1823. 'This class is to provide more functionality for Modes that accommondate other modes.  It provides speedups like painter''s algorithm for drawing and mode based buffering.  Shan July 21, 1989'!
  1824.  
  1825.  
  1826. !ExpandedMode methodsFor: 'layering'!
  1827.  
  1828. computeSubLayeringBelow: aSubView withIn: aRect 
  1829.     "Override to provide painter's algorithm.  Shan April 23, 1989"
  1830.  
  1831.     | subList found |
  1832.     aSubView isNil
  1833.         ifTrue: [found _ true
  1834.             "compute everyone"]
  1835.         ifFalse: [found _ false].
  1836.     subViews ~= nil
  1837.         ifTrue: 
  1838.             [subList _ OrderedCollection new.
  1839.             subViews
  1840.                 reverseDo: 
  1841.                     [:each | 
  1842.                     found
  1843.                         ifTrue: [each computeLayering: subList withIn: aRect]
  1844.                         ifFalse: [each = aSubView ifTrue: [found _ true]].
  1845.                     "This is the only difference between this method and 
  1846.                     the one in Mode.  Shan April 23, 1989"
  1847.                     (painter not and: [each isVisible & each insideColor notNil])
  1848.                         ifTrue: [subList add: each displayBox]]]!
  1849.  
  1850. isPainter
  1851.     "If painter is true,  Shan April 26, 1989"
  1852.  
  1853.     ^ painter!
  1854.  
  1855. setPainter: aBool 
  1856.     "If painter is true, the layering algorithm will not compute the effect 
  1857.     of peer modes for the subModes below me.  Shan April 23, 1989"
  1858.  
  1859.     painter _ aBool! !
  1860.  
  1861. !ExpandedMode methodsFor: 'initialize-release'!
  1862.  
  1863. initialize
  1864.      super initialize.
  1865.     painter _ false! !
  1866.  
  1867. ExpandedMode subclass: #ModeGroup
  1868.     instanceVariableNames: ''
  1869.     classVariableNames: ''
  1870.     poolDictionaries: ''
  1871.     category: 'Modes-Shan'!
  1872. ModeGroup comment:
  1873. 'This class can be used to group modes together.  The shape (involved in event processing and enter/leave business) is defined by the component modes.  Example applications include ShrunkenWindow, LibraryObject, SemObjDelegate, and MessageLink.  Shan August 24, 1989'!
  1874.  
  1875.  
  1876. !ModeGroup methodsFor: 'event handling'!
  1877.  
  1878. interestedIn: event 
  1879.     "This is the part of the event dispatching mechanism that decides  
  1880.     whether the mode should process the event.  Shan August 24, 1989."
  1881.  
  1882.     (super interestedIn: event)
  1883.         ifFalse: [^false].
  1884.     self subModes do: [:each | (each interestedIn: event)
  1885.             ifTrue: [^true]].
  1886.     ^false! !